package com.jprocms.module.cms.controller.admin.site;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.lang.Assert;
import com.jpro.framework.common.pojo.CommonResult;
import com.jprocms.module.cms.api.dto.SiteConfigDto;
import com.jprocms.module.cms.api.dto.SiteDefTplDto;
import com.jprocms.module.cms.api.dto.SiteDefTplQueryDto;
import com.jprocms.module.cms.api.vo.SiteContentDefTplVO;
import com.jprocms.module.cms.api.vo.SiteDefTplVO;
import com.jprocms.module.cms.controller.admin.model.vo.ModelQueryReqVO;
import com.jprocms.module.cms.convert.sitedetailtpl.SiteDetailTplConvert;
import com.jprocms.module.cms.convert.sitetpl.SiteTplConvert;
import com.jprocms.module.cms.dal.dataobject.model.ModelDO;
import com.jprocms.module.cms.dal.dataobject.site.SiteDO;
import com.jprocms.module.cms.dal.dataobject.sitedetailtpl.SiteDetailTplDO;
import com.jprocms.module.cms.dal.dataobject.sitetpl.SiteTplDO;
import com.jprocms.module.cms.enums.EnumModelType;
import com.jprocms.module.cms.service.model.ModelService;
import com.jprocms.module.cms.service.site.SiteService;
import com.jprocms.module.cms.service.sitedetailtpl.SiteDetailTplService;
import com.jprocms.module.cms.service.sitetpl.SiteTplService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.validation.Valid;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;

import static com.jpro.framework.common.exception.util.ServiceExceptionUtil.exception;
import static com.jpro.framework.common.pojo.CommonResult.success;
import static com.jprocms.module.cms.enums.ErrorCodeConstants.SITE_NOT_EXISTS;
import static org.apache.commons.lang3.StringUtils.EMPTY;

/**
 * 站点 配置
 *
 * @author jprocms
 */
@Tag(name = "管理后台 - 站点配置")
@RestController
@RequestMapping("/cms/site/config")
@Validated
public class SiteConfigController {

    @Resource
    private SiteService siteService;
    @Resource
    private SiteTplService siteTplService;
    @Resource
    private ModelService modelService;

    @Resource
    private SiteDetailTplService siteDetailTplService;


    @PostMapping("/update")
    @Operation(summary = "站点配置")
    @PreAuthorize("@ss.hasPermission('cms:site:config:update')")
    public CommonResult<Boolean> updateSiteConfig(@Valid @RequestBody SiteConfigDto configDto) {
        siteService.updateSiteConfig(configDto);
        siteService.clearSiteCache(configDto.getId());
        return success(true);
    }

    @GetMapping("/get")
    @Operation(summary = "获得站点配置")
    @Parameter(name = "id", description = "编号", required = true, example = "1024")
    @PreAuthorize("@ss.hasPermission('cms:site:config:update')")
    public CommonResult<SiteConfigDto> getSiteConfig(@RequestParam("id") Long id) {
        SiteDO site = siteService.getSite(id);
        Assert.notNull(site, () -> {
            throw exception(SITE_NOT_EXISTS);
        });
        return success(site.getSiteConfig());
    }

    @PostMapping("/defTpl/update")
    @Operation(summary = "默认模板配置修改")
    @PreAuthorize("@ss.hasPermission('cms:site:defTpl:update')")
    public CommonResult<Boolean> updateSiteDefTplConfig(@Valid @RequestBody SiteDefTplDto siteDefTplDto) {
        siteService.updateSiteDefTplConfig(siteDefTplDto);
        return success(true);
    }

    @GetMapping("/defTpl/get")
    @Operation(summary = "默认模板配置读取")
    @PreAuthorize("@ss.hasPermission('cms:site:defTpl:update')")
    public CommonResult<SiteDefTplVO> getSiteDefTplConfig(@Valid SiteDefTplQueryDto queryDto) {
        final SiteDO siteDO = siteService.getSite(queryDto.getSiteId());
        SiteTplDO siteTplDO = siteTplService.selectSiteTpl(queryDto);
        List<SiteDetailTplDO> siteDetailTplDOS = siteDetailTplService.selectSiteTpl(queryDto);
        SiteDefTplVO siteTplVO = SiteTplConvert.INSTANCE.joinSuffixConvert(siteTplDO);
        ModelQueryReqVO modelReqVO = new ModelQueryReqVO();
        modelReqVO.setModelType(EnumModelType.CONTENT.getType().shortValue());
        List<ModelDO> modelList = modelService.getModelList(modelReqVO);
        Set<SiteContentDefTplVO> contentDefTpls = siteTplVO.getContentDefTpls();
        Map<Long, SiteContentDefTplVO> modelContentDefTplMap = new HashMap<>();
        CollUtil.toMap(contentDefTpls, modelContentDefTplMap, SiteContentDefTplVO::getModelId);
        List<SiteContentDefTplVO> siteContentDefTplVOS = SiteDetailTplConvert.INSTANCE.joinSuffixConvert(siteDetailTplDOS);
        CollUtil.toMap(contentDefTpls, modelContentDefTplMap, SiteContentDefTplVO::getModelId);
        for (ModelDO modelDO : modelList) {
            SiteContentDefTplVO siteContentDefTplVO = modelContentDefTplMap.get(modelDO.getId());
            String detailTpl = getDetailTpl(modelDO.getId(), siteContentDefTplVOS);
            if (siteContentDefTplVO == null) {
                contentDefTpls.add(new SiteContentDefTplVO(modelDO.getId(), modelDO.getName(), detailTpl));
            } else {
                siteContentDefTplVO.setModelName(modelDO.getName());
                siteContentDefTplVO.setDetailTpl(detailTpl);
            }
        }
        siteTplVO.setPcSolution(siteDO.getPcSolution());
        siteTplVO.setH5Solution(siteDO.getH5Solution());
        return success(siteTplVO);
    }

    private String getDetailTpl(Long modelId, List<SiteContentDefTplVO> siteContentDefTplVOS) {
        if (CollUtil.isEmpty(siteContentDefTplVOS) || modelId == null) {
            return EMPTY;
        }
        List<SiteContentDefTplVO> collect = siteContentDefTplVOS.stream().filter(c -> c.getModelId().equals(modelId)).collect(Collectors.toList());
        if (CollUtil.isEmpty(collect)) {
            return EMPTY;
        }
        return collect.get(0).getDetailTpl();
    }


}
